package com.ledi.guns.modular.ledipay.controller;

import io.swagger.annotations.Api;
import io.swagger.annotations.ApiImplicitParam;
import io.swagger.annotations.ApiImplicitParams;
import io.swagger.annotations.ApiOperation;

import java.io.ByteArrayOutputStream;
import java.io.File;
import java.io.IOException;
import java.io.InputStream;
import java.io.PrintWriter;
import java.io.UnsupportedEncodingException;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.SortedMap;
import java.util.TreeMap;
import java.util.UUID;

import javax.annotation.Resource;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import javax.validation.Valid;

import org.apache.commons.io.FileUtils;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.validation.annotation.Validated;
import org.springframework.web.bind.annotation.PathVariable;
import org.springframework.web.bind.annotation.RequestBody;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestMethod;
import org.springframework.web.bind.annotation.RequestParam;
import org.springframework.web.bind.annotation.RestController;
import org.springframework.web.multipart.MultipartFile;

import com.alibaba.fastjson.JSON;
import com.baomidou.mybatisplus.plugins.Page;
import com.ledi.guns.common.exception.BizExceptionEnum;
import com.ledi.guns.common.exception.BussinessException;
import com.ledi.guns.common.persistence.model.ClassInfo;
import com.ledi.guns.common.persistence.model.vo.ClassInfoVo;
import com.ledi.guns.common.persistence.model.vo.StudentVo;
import com.ledi.guns.core.base.tips.SuccessTip;
import com.ledi.guns.core.base.tips.Tip;
import com.ledi.guns.core.util.PayUtil;
import com.ledi.guns.core.util.SystemConstans;
import com.ledi.guns.core.util.ToPdf;
import com.ledi.guns.core.util.baiduUtil.ActionEnter;
import com.ledi.guns.modular.ledipay.controller.req.ScanCode.Face2FacePay;
import com.ledi.guns.modular.ledipay.controller.req.ScanCode.PayInfo;
import com.ledi.guns.modular.ledipay.controller.req.ScanCode.QueryDetailInfo;
import com.ledi.guns.modular.ledipay.controller.req.ScanCode.SchoolInfo;
import com.ledi.guns.modular.ledipay.controller.req.apply.ApplyCooperateReq;
import com.ledi.guns.modular.ledipay.controller.req.clazz.ClassinfoReq;
import com.ledi.guns.modular.ledipay.controller.req.clazz.StudentReq;
import com.ledi.guns.modular.ledipay.service.ApplyCooperateService;
import com.ledi.guns.modular.ledipay.service.ClassInfoService;
import com.ledi.guns.modular.ledipay.service.IScanCodeService;
import com.ledi.guns.modular.ledipay.service.SmsService;
import com.ledi.guns.modular.ledipay.service.StudentService;
import com.ledi.guns.modular.ledipay.service.impl.BillStreamServiceImpl;
import com.ledi.guns.modular.ledipay.service.impl.SchoolServiceImpl;

/**
 * 文件名称： com.ledi.guns.modular.ledipay.controller.ScanCodeController.java<br/>
 * 初始作者： 许芬<br/>
 * 创建日期： 2018年1月4日<br/>
 * 功能说明： 这里用一句话描述这个类的作用--此句话需删除 <br/>
 * =================================================<br/>
 * 修改记录：<br/>
 * 修改作者 日期 修改内容<br/>
 * ================================================<br/>
 * Copyright (橘子股份-幼儿事业部) 2017-2018.All rights reserved.<br/>
 */
@Api
@RestController
@RequestMapping("/restApi/scan")
@Validated
public class ScanCodeController {

	protected final static Logger logger = LoggerFactory.getLogger(ScanCodeController.class);

	@Autowired
	private IScanCodeService ScanCodeService;
	@Autowired
	BillStreamServiceImpl streamService;
	@Autowired
	private ActionEnter actionEnter;
	@Autowired
	private ClassInfoService classInfoService;

	@Autowired
	private ApplyCooperateService applyCooperateService;
	@Value("${weixin.appid}")
	private String appid;
	@Value("${weixin.prePayUrl}")
	private String prePayUrl;

	@Value("${weixin.facePrePayUrl}")
	private String facePrePayUrl;

	@Value("${weixin.codePayUrl}")
	private String codePayUrl;
	@Value("${weixin.weixinCode}")
	private String weixinCode;

	@Value("${weixin.faceWeixinCode}")
	private String faceWeixinCode;

	@Resource
	private SmsService smsService;

	// 微信跳转到的URL
	@Value("${weixin.h5Url}")
	private String h5Url;

	@Resource
	private SchoolServiceImpl schoolService;
	@Resource
	private StudentService studentService;

	/**
	 * @api {GET} /restApi/scan/pay 扫一扫链接
	 * @apiGroup scan
	 * @apiName pay
	 * @apiParam userId 用户ID
	 * @apiParam schoolId 学校ID
	 */
	@RequestMapping(value = "/pay", method = RequestMethod.GET)
	public void pay(HttpServletRequest request, HttpServletResponse response) {

		String userId = request.getParameter("userId");
		String schoolId = request.getParameter("schoolId");
		String comments = request.getParameter("comments");
		logger.error(comments);
		String redirectUri = prePayUrl + "?userId=" + userId + "&schoolId=" + schoolId + "&comments=" + comments;
		String ua = request.getHeader("user-agent").toLowerCase();
		if (ua.indexOf("micromessenger") > 0) {// 是微信浏览器
			try {
				redirectUri = weixinCode + "?userId=" + userId + "&schoolId=" + schoolId + "&comments=" + comments;
				redirectUri = redirectUri + "&payWay=" + SystemConstans.PAY_WAY_WEIXIN;
				redirectUri = java.net.URLEncoder.encode(redirectUri);
				redirectUri = codePayUrl +
						"?appid=" + appid + "&redirect_uri="
						+ redirectUri
						+ "&response_type=code&state=" + schoolId
						+ "&scope=snsapi_base#wechat_redirect";
				response.sendRedirect(redirectUri);
			} catch (IOException e) {
				e.printStackTrace();
			}
		} else if (ua.indexOf("aplipay") > 0) {// 是支付宝浏览器
			try {
				redirectUri = redirectUri + "&payWay=" + SystemConstans.PAY_WAY_ALI;
				response.sendRedirect(redirectUri);
			} catch (IOException e) {
				e.printStackTrace();
			}
		} else {
			redirectUri = redirectUri + "&payWay=" + SystemConstans.PAY_WAY_ALI;
			try {
				response.sendRedirect(redirectUri);
			} catch (IOException e) {
				e.printStackTrace();
			}
		}

	}

	/**
	 * @api {GET} /restApi/scan/facePay 当面付扫一扫链接
	 * @apiGroup scan
	 * @apiName facePay
	 * @apiParam userId 用户ID
	 * @apiParam schoolId 学校ID
	 * @apiParam comments 签名
	 * @apiParam billId 账单id
	 */
	@RequestMapping(value = "/facePay", method = RequestMethod.GET)
	public void facePay(HttpServletRequest request, HttpServletResponse response) {

		String userId = request.getParameter("userId");
		String schoolId = request.getParameter("schoolId");
		String comments = request.getParameter("comments");
		String billId = request.getParameter("billId");
		logger.error(comments);
		String redirectUri = facePrePayUrl + "?userId=" + userId + "&schoolId=" + schoolId + "&comments=" + comments + "&billId=" + billId;
		String ua = request.getHeader("user-agent").toLowerCase();
		if (ua.indexOf("micromessenger") > 0) {// 是微信浏览器
			try {
				redirectUri = faceWeixinCode + "?userId=" + userId + "&schoolId=" + schoolId + "&comments=" + comments + "&billId=" + billId;
				redirectUri = redirectUri + "&payWay=" + SystemConstans.PAY_WAY_WEIXIN;
				redirectUri = java.net.URLEncoder.encode(redirectUri);
				redirectUri = codePayUrl +
						"?appid=" + appid + "&redirect_uri="
						+ redirectUri
						+ "&response_type=code&state=" + schoolId
						+ "&scope=snsapi_base#wechat_redirect";
				response.sendRedirect(redirectUri);
			} catch (IOException e) {
				e.printStackTrace();
			}
		} else if (ua.indexOf("aplipay") > 0) {// 是支付宝浏览器
			try {
				redirectUri = redirectUri + "&payWay=" + SystemConstans.PAY_WAY_ALI;
				response.sendRedirect(redirectUri);
			} catch (IOException e) {
				e.printStackTrace();
			}
		} else {
			redirectUri = redirectUri + "&payWay=" + SystemConstans.PAY_WAY_ALI;
			try {
				response.sendRedirect(redirectUri);
			} catch (IOException e) {
				e.printStackTrace();
			}
		}

	}

	@RequestMapping(value = "/weixinCode", method = RequestMethod.GET)
	public void weixinCode(HttpServletRequest request, HttpServletResponse response) {

		logger.error("-------------------url=" + request.getRequestURL());

		// 获取用户的code
		String code = request.getParameter("code");
		// 获取用户的userId
		String userId = request.getParameter("userId");
		// 获取学校ID
		String schoolId = request.getParameter("schoolId");
		// 获取支付方式
		String payWay = request.getParameter("payWay");
		// 获取签名
		String comments = request.getParameter("comments");
		logger.error(comments);
		try {
			response.sendRedirect(
					prePayUrl + "?userId=" + userId + "&schoolId=" + schoolId + "&code=" + code + "&payWay=" + payWay
					+ "&comments=" + comments);
		} catch (IOException e) {
			e.printStackTrace();
		}

	}

	@RequestMapping(value = "/faceWeixinCode", method = RequestMethod.GET)
	public void faceWeixinCode(HttpServletRequest request, HttpServletResponse response) {

		logger.error("-------------------url=" + request.getRequestURL());

		// 获取用户的code
		String code = request.getParameter("code");
		// 获取用户的userId
		String userId = request.getParameter("userId");
		// 获取学校ID
		String schoolId = request.getParameter("schoolId");
		// 获取支付方式
		String payWay = request.getParameter("payWay");
		// 获取签名
		String comments = request.getParameter("comments");

		String billId = request.getParameter("billId");
		logger.error(comments);
		try {
			response.sendRedirect(
					facePrePayUrl + "?userId=" + userId + "&schoolId=" + schoolId + "&code=" + code + "&payWay=" + payWay
					+ "&comments=" + comments + "&billId=" + billId);
		} catch (IOException e) {
			e.printStackTrace();
		}

	}

	/**
	 * @api {POST} /restApi/scan/prePay 发送账单
	 * @apiGroup scan
	 * @apiName prePay
	 * @apiParam userId 用户ID
	 * @apiParam schoolId 学校ID
	 * @apiParam classId 班级ID
	 * @apiParam studentName 学生名字
	 * @apiParam parentMobile 家长手机号
	 * @apiParam itemName 项目名称
	 * @apiParam totalDetail 缴费金额
	 * @apiParam code 获取到的微信Code
	 * @apiParam payWay 缴费方式(ALIPAY:支付宝，WEIXIN:微信支付)
	 * @apiSuccess prepay_id 微信预支付ID
	 * @apiSuccess sign 微信返回签名
	 * @apiSuccess nonce_str 微信返回随机码
	 * @apiSuccessExample {json} Success-Response:
	 *                    {
	 *                    "code": 200,
	 *                    "data": {
	 *                    "prepay_id": 62,
	 *                    "sign": 3,
	 *                    "status": 2,
	 *                    "nonce_str": 3
	 *                    },
	 *                    "message": "成功"
	 *                    }
	 * @apiVersion 1.1.0
	 */
	@RequestMapping(value = "/prePay", method = RequestMethod.POST)
	public Tip PrePay(@RequestBody @Valid PayInfo payInfo, HttpServletRequest request, HttpServletResponse response) {

		Map<String, String> pay = ScanCodeService.pay(payInfo, request, response);

		return SuccessTip.buildSuccess(pay);
	}

	/**
	 * @api {POST} /restApi/scan/face2FacePrePay 当面付缴费账单
	 * @apiGroup scan
	 * @apiName face2FacePrePay
	 * @apiParam {int} userId 用户ID
	 * @apiParam {int} schoolId 学校ID
	 * @apiParam {int} classId 班级ID
	 * @apiParam {int} billId 账单ID
	 * @apiParam {String} studentName 学生名字
	 * @apiParam {String} parentMobile 家长手机号
	 * @apiParam {String} itemName 备注
	 * @apiParam {String} code 获取到的微信Code
	 * @apiParam {String} sign 签名
	 * @apiParam {String} payWay 缴费方式(ALIPAY:支付宝，WEIXIN:微信支付)
	 * @apiSuccess {String} prepay_id 微信预支付ID
	 * @apiSuccess {String} sign 微信返回签名
	 * @apiSuccess {String} nonce_str 微信返回随机码
	 * @apiParamExample {json} Request-Example:
	 *                  {
	 *                  "billId": 558,
	 *                  "className": "火箭班",
	 *                  "comments": "一年级学费",
	 *                  "parentMobile": "17625320526",
	 *                  "payWay": "ALIPAY",
	 *                  "schoolId": 228,
	 *                  "sign": "CB8612BC9F0A9922FC20C69D99721DF6",
	 *                  "studentName": "钟小平",
	 *                  "userId":63
	 *                  }
	 * @apiSuccessExample {json} Success-Response:
	 *                    {
	 *                    "code": 200,
	 *                    "data": {
	 *                    "prepay_id": 62,
	 *                    "sign": 3,
	 *                    "status": 2,
	 *                    "nonce_str": 3
	 *                    },
	 *                    "message": "成功"
	 *                    }
	 *                    {
	 *                    "code": 200,
	 *                    "data": {
	 *                    "resultUrl":
	 *                    "https%3A%2F%2Fopenauth.alipay.com%2Foauth2%2FpublicAppAuthorize.htm%3Fapp_id%3D2016112803504802%26scope%3Dauth_base%26redirect_uri%3Dhttps%3A%2F%2Fk12jiaofei.alipay-eco.com%2Fcallback%2Fhome%3Ftype%3D7%26isvNo%3D5a1d4569dc5e35329a6f39ec%26schoolCode%3D32050100000001%26studentNo%3Dnull%26value%3D17625320526%26orderno%3D5b7f769270935d5aa95eb81c%26__webview_options__%3DpullRefresh%253DYES"
	 *                    ,
	 *                    "payWay": "ALIPAY",
	 *                    "billDetailId": "180824110abzju36cc"
	 *                    },
	 *                    "message": "成功"
	 *                    }
	 * @apiVersion 1.4.0
	 */
	@RequestMapping(value = "/face2FacePrePay", method = RequestMethod.POST)
	public Tip face2FacePrePay(@RequestBody @Valid Face2FacePay payInfo, HttpServletRequest request, HttpServletResponse response) {

		Map<String, String> pay = ScanCodeService.face2FacePrePay(payInfo, request, response);
		return SuccessTip.buildSuccess(pay);
	}

	/**
	 * 提交支付后的微信异步返回接口
	 */
	@RequestMapping(value = "/weixinNotify")
	public void weixinNotify(HttpServletRequest request, HttpServletResponse response) {

		try {
			InputStream inStream = request.getInputStream();
			ByteArrayOutputStream outSteam = new ByteArrayOutputStream();
			byte[] buffer = new byte[1024];
			int len = 0;
			while ((len = inStream.read(buffer)) != -1) {
				outSteam.write(buffer, 0, len);
			}
			outSteam.close();
			inStream.close();
			String resultStr = new String(outSteam.toByteArray(), "utf-8");
			logger.info("支付成功的回调：" + resultStr);
			ScanCodeService.weixinNotify(resultStr);
			// 通知微信.异步确认成功
			response.getWriter().write(PayUtil.setXML("SUCCESS", ""));
		} catch (Exception e) {
			logger.error("微信回调接口出现错误：", e);
			try {
				response.getWriter().write(PayUtil.setXML("FAIL", "error"));
			} catch (IOException e1) {
				e1.printStackTrace();
			}
		}

	}

	/**
	 * @api {GET} /restApi/scan/findSchoolInfo/{id} 获取学校信息
	 * @apiGroup scan
	 * @apiName findSchoolInfo
	 * @apiParam id 学校ID
	 * @apiSuccess id 学校ID
	 * @apiSuccess schoolName 学校名称
	 * @apiSuccess classId 班级ID
	 * @apiSuccess className 班级名称
	 * @apiSuccessExample {json} Success-Response:
	 *                    {
	 *                    "code":200,
	 *                    "data":{
	 *                    "classInfoList":[
	 *                    {
	 *                    "className":"小一班",
	 *                    "id":6
	 *                    },{
	 *                    "className":"小二班",
	 *                    "id":11
	 *                    }
	 *                    ],
	 *                    "id":1,
	 *                    "studentName":"乐迪yuyu"
	 *                    },
	 *                    "message":"成功"
	 *                    }
	 * @apiVersion 1.1.0
	 */
	@RequestMapping(value = "/findSchoolInfo/{id}", method = RequestMethod.GET)
	public Tip findSchoolInfo(@PathVariable("id") Long id) {

		SchoolInfo schoolInfo = ScanCodeService.findSchoolInfo(id);

		return SuccessTip.buildSuccess(schoolInfo);
	}

	/**
	 * @api {GET} /restApi/scan/findDetailInfo/{id} 获取学校信息
	 * @apiGroup scan
	 * @apiName findDetailInfo
	 * @apiParam id 账单明细ID
	 * @apiSuccess id 学校ID
	 * @apiSuccess schoolName 学校名称
	 * @apiSuccess classId 班级ID
	 * @apiSuccess className 班级名称
	 * @apiSuccessExample {json} Success-Response:
	 *                    {
	 *                    "code":200,
	 *                    "data":{
	 *                    "classInfoList":[
	 *                    {
	 *                    "className":"小一班",
	 *                    "id":6
	 *                    },{
	 *                    "className":"小二班",
	 *                    "id":11
	 *                    }
	 *                    ],
	 *                    "id":1,
	 *                    "studentName":"乐迪yuyu"
	 *                    },
	 *                    "message":"成功"
	 *                    }
	 * @apiVersion 1.1.0
	 */
	@RequestMapping(value = "/findDetailInfo/{billDetailId}", method = RequestMethod.GET)
	public Tip findDetailInfo(@PathVariable("billDetailId") String billDetailId) {

		QueryDetailInfo queryDetailInfo = ScanCodeService.findDetailInfo(billDetailId);

		return SuccessTip.buildSuccess(queryDetailInfo);
	}

	/**
	 * @api {POST} /restApi/scan/download 图片转PDF文档
	 * @apiGroup scan
	 * @apiName download
	 * @apiParam {File} file 图片(大小:2M)
	 * @apiSuccess {String} data 文件相对路径
	 * @apiError 2500 文件过大错误
	 */
	@ApiOperation("download")
	@ApiImplicitParams({
		@ApiImplicitParam(dataType = "file", name = "file", required = true, paramType = "form")
	})
	@RequestMapping(value = "/download", method = RequestMethod.POST)
	public void uploadFile(
			@RequestParam(value = "file", required = true) MultipartFile file, HttpServletResponse resp) throws Exception {

		String fileName = file.getOriginalFilename();

		String fileType = fileName.substring(fileName.lastIndexOf(".") + 1, fileName.length());
		if (file.getBytes().length > 2 * 1024 * 1024) {
			throw new BussinessException(BizExceptionEnum.FILE_LENGTH_BIGGER);
		}

		File outputFile = getFile(fileName.substring(0, fileName.lastIndexOf(".")) + ".pdf");
		File image = getFile(fileName);
		file.transferTo(image);
		ToPdf.imgMerageToPdf(image, outputFile, resp);
	}

	public static String singleUpload(MultipartFile file) {

		String tempFileName = UUID.randomUUID().toString();
		String path = FileUtils.getTempDirectoryPath();
		path = path + File.separator + tempFileName;
		File file2 = new File(path);
		try {
			file.transferTo(file2);
		} catch (IllegalStateException | IOException e) {
			logger.error("解析错误");
		}
		return tempFileName;
	}

	public static File getFile(String fileName) {

		String path = FileUtils.getTempDirectoryPath();
		path = path + File.separator + fileName;
		File file = new File(path);
		return file;
	}

	/**
	 * @api {GET} /restApi/scan/scanSms 扫一扫链接短信支付
	 * @apiGroup scan
	 * @apiName scanSms
	 * @apiParam orderNo 订单编码
	 * @apiParam userMobile 用户手机号
	 * @apiParam sign 签名
	 * @apiSuccess msg 如果校验不通过则有值校验通过的话为空
	 * @apiSuccess payWay 支付方式（weixin：微信，alipay：支付宝）
	 * @apiSuccess orderSign 微信支付才有（签名）
	 * @apiSuccess orderStr 支付宝支付才有url
	 * @apiSuccess state 微信支付才有（订单编号）
	 */
	@RequestMapping(value = "/scanSms", method = RequestMethod.GET)
	public void scan(HttpServletRequest request, HttpServletResponse response) {

		// 获取参数
		// 获取参数
		String userMobile = request.getParameter("userMobile");
		String orderNo = request.getParameter("orderNo");
		String sign = request.getParameter("sign");
		logger.info(orderNo);
		logger.info(userMobile);
		logger.info(sign);

		// 检验参数是否合法
		String msg = smsService.scan(userMobile, orderNo, sign);
		if (msg != null) {
			try {
				// 如果出错，直接跳转到H5页面
				response.sendRedirect(h5Url + "?msg=" + msg);
				return;
			} catch (IOException e) {
				e.printStackTrace();
			}
		}
		String ua = request.getHeader("user-agent").toLowerCase();
		if (ua.indexOf("micromessenger") > 0) {// 是微信浏览器

			logger.info("微信：micromessenger");
			try {
				SortedMap<String, String> orderSign = new TreeMap<String, String>();
				orderSign.put("orderNo", orderNo);
				orderSign.put("key", SystemConstans.ORDER_PAY_WAY_WEIXIN);
				String orderSigns = PayUtil.createSign(orderSign);
				String redirectUri = h5Url + "?payWay=" + SystemConstans.ORDER_PAY_WAY_WEIXIN + "&orderSign="
						+ orderSigns;
				logger.error(redirectUri);
				redirectUri = java.net.URLEncoder.encode(redirectUri);
				redirectUri = codePayUrl +
						"?appid=" + appid + "&redirect_uri="
						+ redirectUri
						+ "&response_type=code&state=" + orderNo
						+ "&scope=snsapi_base#wechat_redirect";
				response.sendRedirect(redirectUri);
			} catch (IOException e) {
				e.printStackTrace();
			}
		} else if (ua.indexOf("aplipay") > 0) {// 是支付宝浏览器

			logger.info("支付宝浏览器：aplipay");
			try {
				String orderStr = smsService.prePayOrder(orderNo);
				logger.info("订单字符串orderStr:{}", orderStr);
				String redirectUri = h5Url + "?orderStr=" + orderStr + "&payWay="
						+ SystemConstans.ORDER_PAY_WAY_ALIPAY + "&orderNo=" + orderNo;
				logger.error(redirectUri);
				response.sendRedirect(redirectUri);
			} catch (IOException e) {
				e.printStackTrace();
			}
		} else {// 其他浏览器也用支付宝支付
			try {
				logger.info("其他浏览器：micromessenger");
				String orderStr = smsService.prePayOrder(orderNo);
				orderStr = java.net.URLEncoder.encode(orderStr);
				logger.info("订单字符串orderStr:{}", orderStr);
				String redirectUri = h5Url + "?orderStr=" + orderStr + "&payWay="
						+ SystemConstans.ORDER_PAY_WAY_ALIPAY + "&orderNo=" + orderNo;
				logger.error(redirectUri);
				response.sendRedirect(redirectUri);
			} catch (IOException e) {
				e.printStackTrace();
			}
		}
	}

	/**
	 * @api {GET} /restApi/scan/smsWeixinNotify 提交支付后的微信异步返回接口
	 * @apiGroup scan
	 * @apiName smsWeixinNotify
	 */
	@RequestMapping(value = "/smsWeixinNotify", method = RequestMethod.POST)
	public void smsWeixinNotify(HttpServletRequest request, HttpServletResponse response) {

		try {
			InputStream inStream = request.getInputStream();
			ByteArrayOutputStream outSteam = new ByteArrayOutputStream();
			byte[] buffer = new byte[1024];
			int len = 0;
			while ((len = inStream.read(buffer)) != -1) {
				outSteam.write(buffer, 0, len);
			}
			outSteam.close();
			inStream.close();
			String resultStr = new String(outSteam.toByteArray(), "utf-8");
			logger.info("收到微信支付的回调：{}", resultStr);
			smsService.weixinNotify(resultStr);
			// 通知微信.异步确认成功
			response.getWriter().write(PayUtil.setXML("SUCCESS", ""));
		} catch (Exception e) {
			try {
				response.getWriter().write(PayUtil.setXML("FAIL", "error"));
			} catch (IOException e1) {
				e1.printStackTrace();
			}
		}

	}

	/**
	 * @api {GET} /restApi/scan/alipayNotify 提交支付后的支付宝异步返回接口
	 * @apiGroup scan
	 * @apiName alipayNotify
	 */
	@RequestMapping(value = "/alipayNotify")
	public void alipayNotify(HttpServletRequest request, PrintWriter out) {

		logger.info("收到支付宝支付的回调：------------------>start");

		Map<String, String> params = new HashMap<String, String>();
		Map<?, ?> requestParams = request.getParameterMap();
		for (Object name2 : requestParams.keySet()) {
			String name = (String) name2;
			String[] values = (String[]) requestParams.get(name);
			String valueStr = "";
			for (int i = 0; i < values.length; i++) {
				valueStr = i == values.length - 1 ? valueStr + values[i] : valueStr + values[i] + ",";
			}
			// 乱码解决，这段代码在出现乱码时使用。
			try {
				valueStr = new String(valueStr.getBytes("ISO-8859-1"), "utf-8");
			} catch (UnsupportedEncodingException e) {
				logger.error(e.getMessage(), e);
			}
			params.put(name, valueStr);
		}
		logger.info("收到支付宝支付的回调：{}", params.toString());
		// TRADE_SUCCESS 支付成功
		String trade_status = params.get("trade_status");
		String handleRes = "fail";
		if (trade_status.equalsIgnoreCase("TRADE_SUCCESS")) {
			smsService.alipayNotify(params);
			handleRes = "success";
		}

		logger.info("handleRes=" + handleRes);
		out.write(handleRes);
		out.close();
		return;

	}

	/**
	 * @api {GET} /restApi/scan/sendMsg 赠送每月短信
	 * @apiGroup scan
	 * @apiName sendMsg
	 */
	@RequestMapping(value = "/sendMsg")
	public void alipayNotify() {

		smsService.giveSchoolsms();

	}

	/**
	 * @api {GET} /restApi/scan/schoolClassList/{schoolId} 学校全部班级列表
	 * @apiGroup scan
	 * @apiName schoolClassList
	 * @apiParam {String} schoolId 学校id
	 * @apiSuccess id 班级ID
	 * @apiSuccess name 班级名称
	 * @apiSuccess gradeId 年级id
	 * @apiSuccess gradeName 年级名称
	 * @apiSuccess studentCount 学生数目
	 * @apiSuccess teachers 代课老师
	 * @apiSuccess code 返回编码（200成功）
	 * @apiSuccess message 返回说明
	 * @apiSuccessExample {json} Success-Response:
	 *                    {
	 *                    "code": 200,
	 *                    "data": [
	 *                    {
	 *                    "createTime": "2018-07-10 15:16:59",
	 *                    "creatorId": 95,
	 *                    "creatorRole": "6,9",
	 *                    "gradeId": "",
	 *                    "id": 1153,
	 *                    "isDelete": 0,
	 *                    "name": "2",
	 *                    "orderNum": "",
	 *                    "schoolId": 29,
	 *                    "schoolYear": "",
	 *                    "updateTime": "",
	 *                    "updaterId": "",
	 *                    "updaterRole": "",
	 *                    "versionNo": 0
	 *                    },
	 *                    {
	 *                    "createTime": "2018-07-10 15:18:07",
	 *                    "creatorId": 95,
	 *                    "creatorRole": "6,9",
	 *                    "gradeId": "",
	 *                    "id": 1154,
	 *                    "isDelete": 0,
	 *                    "name": "123123",
	 *                    "orderNum": "",
	 *                    "schoolId": 29,
	 *                    "schoolYear": "",
	 *                    "updateTime": "",
	 *                    "updaterId": "",
	 *                    "updaterRole": "",
	 *                    "versionNo": 0
	 *                    },
	 *                    {
	 *                    "createTime": "2018-07-17 18:06:55",
	 *                    "creatorId": 95,
	 *                    "creatorRole": "6,9",
	 *                    "gradeId": "",
	 *                    "id": 1155,
	 *                    "isDelete": 0,
	 *                    "name": "123",
	 *                    "orderNum": "",
	 *                    "schoolId": 29,
	 *                    "schoolYear": "",
	 *                    "updateTime": "",
	 *                    "updaterId": "",
	 *                    "updaterRole": "",
	 *                    "versionNo": 0
	 *                    },
	 *                    {
	 *                    "createTime": "2018-07-17 18:07:07",
	 *                    "creatorId": 95,
	 *                    "creatorRole": "6,9",
	 *                    "gradeId": "",
	 *                    "id": 1156,
	 *                    "isDelete": 0,
	 *                    "name": "是成本是吃不吃v",
	 *                    "orderNum": "",
	 *                    "schoolId": 29,
	 *                    "schoolYear": "",
	 *                    "updateTime": "",
	 *                    "updaterId": "",
	 *                    "updaterRole": "",
	 *                    "versionNo": 0
	 *                    },
	 *                    {
	 *                    "createTime": "2018-07-17 18:10:37",
	 *                    "creatorId": 95,
	 *                    "creatorRole": "6,9",
	 *                    "gradeId": 4,
	 *                    "id": 1157,
	 *                    "isDelete": 0,
	 *                    "name": "12312",
	 *                    "orderNum": 4,
	 *                    "schoolId": 29,
	 *                    "schoolYear": "",
	 *                    "updateTime": "2018-08-21 13:53:42",
	 *                    "updaterId": 95,
	 *                    "updaterRole": "6,9",
	 *                    "versionNo": 1
	 *                    },
	 *                    {
	 *                    "createTime": "2018-07-19 15:38:07",
	 *                    "creatorId": 95,
	 *                    "creatorRole": "6,9",
	 *                    "gradeId": "",
	 *                    "id": 1158,
	 *                    "isDelete": 0,
	 *                    "name": "124124",
	 *                    "orderNum": "",
	 *                    "schoolId": 29,
	 *                    "schoolYear": "",
	 *                    "updateTime": "",
	 *                    "updaterId": "",
	 *                    "updaterRole": "",
	 *                    "versionNo": 0
	 *                    },
	 *                    {
	 *                    "createTime": "2018-07-19 15:38:25",
	 *                    "creatorId": 95,
	 *                    "creatorRole": "6,9",
	 *                    "gradeId": "",
	 *                    "id": 1159,
	 *                    "isDelete": 0,
	 *                    "name": "124421",
	 *                    "orderNum": "",
	 *                    "schoolId": 29,
	 *                    "schoolYear": "",
	 *                    "updateTime": "",
	 *                    "updaterId": "",
	 *                    "updaterRole": "",
	 *                    "versionNo": 0
	 *                    },
	 *                    {
	 *                    "createTime": "2018-07-26 16:26:16",
	 *                    "creatorId": 95,
	 *                    "creatorRole": "6,9",
	 *                    "gradeId": "",
	 *                    "id": 1164,
	 *                    "isDelete": 0,
	 *                    "name": "dsfdsd",
	 *                    "orderNum": "",
	 *                    "schoolId": 29,
	 *                    "schoolYear": "",
	 *                    "updateTime": "",
	 *                    "updaterId": "",
	 *                    "updaterRole": "",
	 *                    "versionNo": 0
	 *                    },
	 *                    {
	 *                    "createTime": "2018-07-26 16:26:40",
	 *                    "creatorId": 95,
	 *                    "creatorRole": "6,9",
	 *                    "gradeId": "",
	 *                    "id": 1165,
	 *                    "isDelete": 0,
	 *                    "name": "32",
	 *                    "orderNum": "",
	 *                    "schoolId": 29,
	 *                    "schoolYear": "",
	 *                    "updateTime": "",
	 *                    "updaterId": "",
	 *                    "updaterRole": "",
	 *                    "versionNo": 0
	 *                    },
	 *                    {
	 *                    "createTime": "2018-07-26 20:06:06",
	 *                    "creatorId": 95,
	 *                    "creatorRole": "6,9",
	 *                    "gradeId": "",
	 *                    "id": 1166,
	 *                    "isDelete": 0,
	 *                    "name": "fggf",
	 *                    "orderNum": "",
	 *                    "schoolId": 29,
	 *                    "schoolYear": "",
	 *                    "updateTime": "",
	 *                    "updaterId": "",
	 *                    "updaterRole": "",
	 *                    "versionNo": 0
	 *                    },
	 *                    {
	 *                    "createTime": "2018-07-26 20:12:35",
	 *                    "creatorId": 95,
	 *                    "creatorRole": "6,9",
	 *                    "gradeId": "",
	 *                    "id": 1167,
	 *                    "isDelete": 0,
	 *                    "name": "sdsadaa",
	 *                    "orderNum": "",
	 *                    "schoolId": 29,
	 *                    "schoolYear": "",
	 *                    "updateTime": "",
	 *                    "updaterId": "",
	 *                    "updaterRole": "",
	 *                    "versionNo": 0
	 *                    },
	 *                    {
	 *                    "createTime": "2018-08-17 16:25:51",
	 *                    "creatorId": 95,
	 *                    "creatorRole": "6,9",
	 *                    "gradeId": 2,
	 *                    "id": 1170,
	 *                    "isDelete": 0,
	 *                    "name": "123",
	 *                    "orderNum": 123,
	 *                    "schoolId": 29,
	 *                    "schoolYear": "",
	 *                    "updateTime": "",
	 *                    "updaterId": "",
	 *                    "updaterRole": "",
	 *                    "versionNo": 0
	 *                    },
	 *                    {
	 *                    "createTime": "2018-08-17 16:33:56",
	 *                    "creatorId": 95,
	 *                    "creatorRole": "6,9",
	 *                    "gradeId": 1,
	 *                    "id": 1171,
	 *                    "isDelete": 0,
	 *                    "name": "1111",
	 *                    "orderNum": 7,
	 *                    "schoolId": 29,
	 *                    "schoolYear": "",
	 *                    "updateTime": "",
	 *                    "updaterId": "",
	 *                    "updaterRole": "",
	 *                    "versionNo": 0
	 *                    },
	 *                    {
	 *                    "createTime": "2018-08-21 13:49:49",
	 *                    "creatorId": 95,
	 *                    "creatorRole": "6,9",
	 *                    "gradeId": 1,
	 *                    "id": 1174,
	 *                    "isDelete": 0,
	 *                    "name": "gg",
	 *                    "orderNum": 11,
	 *                    "schoolId": 29,
	 *                    "schoolYear": "",
	 *                    "updateTime": "",
	 *                    "updaterId": "",
	 *                    "updaterRole": "",
	 *                    "versionNo": 0
	 *                    }
	 *                    ],
	 *                    "message": "成功"
	 *                    }
	 * @apiVersion 1.4.0
	 */
	@RequestMapping(value = "/schoolClassList/{schoolId}", method = RequestMethod.GET)
	public Tip schoolClassList(@PathVariable("schoolId") Long schoolId) {

		List<ClassInfo> list = classInfoService.findAll(schoolId);
		return SuccessTip.buildSuccess(list);
	}

	/**
	 * @api {GET} /restApi/scan/getClassByBillId?billId=1 学校账单对应班级列表
	 * @apiGroup scan
	 * @apiName getClassByBillId
	 * @apiParam {Long} billId 账单id
	 * @apiSuccess key 班级ID
	 * @apiSuccess value 班级名称
	 * @apiSuccess code 返回编码（200成功）
	 * @apiSuccess message 返回说明
	 * @apiSuccessExample {json} Success-Response:
	 *                    {
	 *                    "code": 200,
	 *                    "data": [
	 *                    {
	 *                    "key": 6,
	 *                    "value": "小一班"
	 *                    }
	 *                    ],
	 *                    "message": "成功"
	 *                    }
	 * @apiVersion 1.4.0
	 */
	@RequestMapping(value = "/getClassByBillId", method = RequestMethod.GET)
	public Tip getClassByBillId(@RequestParam(required = false, value = "billId") Long billId) {

		List<ClassInfoVo> list = classInfoService.getClassByBillId(billId);
		return SuccessTip.buildSuccess(list);
	}

	/**
	 * @api {GET} /restApi/scan/listBillSchoolPayItem/{billId}/{schoolId} 学校账单收费项列表
	 * @apiGroup scan
	 * @apiName listBillSchoolPayItem
	 * @apiParam {int} billId 账单id
	 * @apiParam {int} schoolId 学校id
	 * @apiSuccess {int} flag 0非必须，1必须，2，退款
	 * @apiSuccess {int} name 收费项名称
	 * @apiSuccess {int} money 收费金额
	 * @apiSuccess {int} billName 账单名称
	 * @apiVersion 1.4.0
	 * @apiSuccessExample {json} Success-Response:
	 *                    {
	 *                    "code": 200,
	 *                    "data": {
	 *                    "billId": 229,
	 *                    "billName": "123",
	 *                    "payItems": [
	 *                    {
	 *                    "createTime": "2018-08-20 17:48:07",
	 *                    "creatorId": 95,
	 *                    "creatorRole": "6,9",
	 *                    "flag": 0,
	 *                    "id": 2,
	 *                    "isDelete": 0,
	 *                    "money": 3,
	 *                    "name": "xuzong",
	 *                    "remark": "123",
	 *                    "schoolId": 29,
	 *                    "updateTime": "2018-08-21 10:08:26",
	 *                    "updaterId": 95,
	 *                    "updaterRole": "6,9",
	 *                    "versionNo": 2
	 *                    }
	 *                    ]
	 *                    },
	 *                    "message": "成功"
	 *                    }
	 */
	@RequestMapping(value = "/listBillSchoolPayItem/{billId}/{schoolId}", method = RequestMethod.GET)
	public Tip listBillSchoolPayItem(@PathVariable("billId") Long billId, @PathVariable("schoolId") Long schoolId) {

		return SuccessTip.buildSuccess(schoolService.listSchoolPayItemByBillId(billId, schoolId));
	}

	/**
	 * @api {POST} /restApi/scan/studentList 学生列表
	 * @apiGroup scan
	 * @apiName studentList
	 * @apiParam {int} classId 班级Id
	 * @apiParam {String} gradeId 年级id
	 * @apiParam {String} name 学生姓名
	 * @apiParam {String} parentMobile 班级名称
	 * @apiVersion 1.4.0
	 * @apiSuccessExample {json} Success-Response:
	 *                    {
	 *                    "code": 200,
	 *                    "message": "成功"
	 *                    }
	 */
	@RequestMapping(value = "/studentList", method = RequestMethod.POST)
	public Tip studentList(@RequestBody StudentReq studentReq) {

		studentReq.checkOrder(StudentVo.class);
		Page<StudentVo> page = studentService.studentList(new Page<StudentVo>(studentReq.getPageNo(), studentReq.getPageSize()), studentReq);
		return SuccessTip.buildSuccess(page);
	}

	/**
	 * @api {POST} /restApi/scan/classList 班级列表
	 * @apiGroup scan
	 * @apiName classList
	 * @apiParam {String} schoolId 学校id
	 * @apiSuccess id 班级ID
	 * @apiSuccess name 班级名称
	 * @apiSuccess gradeId 年级id
	 * @apiSuccess gradeName 年级名称
	 * @apiSuccess studentCount 学生数目
	 * @apiSuccess teachers 代课老师
	 * @apiSuccess code 返回编码（200成功）
	 * @apiSuccess message 返回说明
	 * @apiSuccessExample {json} Success-Response:
	 *                    {
	 *                    "code": 200,
	 *                    "data": {
	 *                    "asc": true,
	 *                    "condition": "",
	 *                    "current": 1,
	 *                    "limit": 2147483647,
	 *                    "offset": 0,
	 *                    "offsetCurrent": 0,
	 *                    "openSort": true,
	 *                    "orderByField": "",
	 *                    "pages": 115,
	 *                    "records": [
	 *                    {
	 *                    "createTime": "2018-08-17 11:22:06",
	 *                    "gradeId": "",
	 *                    "gradeName": "",
	 *                    "id": 1168,
	 *                    "name": "胡旭阳班",
	 *                    "studentCount": "",
	 *                    "teachers": "",
	 *                    "versionNo": 0
	 *                    },
	 *                    {
	 *                    "createTime": "2018-07-19 16:02:05",
	 *                    "gradeId": "",
	 *                    "gradeName": "",
	 *                    "id": 1160,
	 *                    "name": "123123",
	 *                    "studentCount": "",
	 *                    "teachers": "",
	 *                    "versionNo": 0
	 *                    },
	 *                    {
	 *                    "createTime": "2017-12-19 16:44:00",
	 *                    "gradeId": "",
	 *                    "gradeName": "",
	 *                    "id": 1152,
	 *                    "name": "小1135班",
	 *                    "studentCount": "",
	 *                    "teachers": "",
	 *                    "versionNo": 0
	 *                    },
	 *                    {
	 *                    "createTime": "2017-12-19 16:44:00",
	 *                    "gradeId": "",
	 *                    "gradeName": "",
	 *                    "id": 1151,
	 *                    "name": "小1134班",
	 *                    "studentCount": "",
	 *                    "teachers": "",
	 *                    "versionNo": 0
	 *                    },
	 *                    {
	 *                    "createTime": "2017-12-19 16:44:00",
	 *                    "gradeId": "",
	 *                    "gradeName": "",
	 *                    "id": 1150,
	 *                    "name": "小1133班",
	 *                    "studentCount": "",
	 *                    "teachers": "",
	 *                    "versionNo": 0
	 *                    },
	 *                    {
	 *                    "createTime": "2017-12-19 16:44:00",
	 *                    "gradeId": "",
	 *                    "gradeName": "",
	 *                    "id": 1149,
	 *                    "name": "小1132班",
	 *                    "studentCount": "",
	 *                    "teachers": "",
	 *                    "versionNo": 0
	 *                    },
	 *                    {
	 *                    "createTime": "2017-12-19 16:44:00",
	 *                    "gradeId": "",
	 *                    "gradeName": "",
	 *                    "id": 1148,
	 *                    "name": "小1131班",
	 *                    "studentCount": "",
	 *                    "teachers": "",
	 *                    "versionNo": 0
	 *                    },
	 *                    {
	 *                    "createTime": "2017-12-19 16:44:00",
	 *                    "gradeId": "",
	 *                    "gradeName": "",
	 *                    "id": 1147,
	 *                    "name": "小1130班",
	 *                    "studentCount": "",
	 *                    "teachers": "",
	 *                    "versionNo": 0
	 *                    },
	 *                    {
	 *                    "createTime": "2017-12-19 16:44:00",
	 *                    "gradeId": "",
	 *                    "gradeName": "",
	 *                    "id": 1146,
	 *                    "name": "小1129班",
	 *                    "studentCount": "",
	 *                    "teachers": "",
	 *                    "versionNo": 0
	 *                    },
	 *                    {
	 *                    "createTime": "2017-12-19 16:44:00",
	 *                    "gradeId": "",
	 *                    "gradeName": "",
	 *                    "id": 1145,
	 *                    "name": "小1128班",
	 *                    "studentCount": "",
	 *                    "teachers": "",
	 *                    "versionNo": 0
	 *                    }
	 *                    ],
	 *                    "searchCount": true,
	 *                    "size": 10,
	 *                    "total": 1146
	 *                    },
	 *                    "message": "成功"
	 *                    }
	 * @apiVersion 1.4.0
	 */
	@RequestMapping(value = "/classList", method = RequestMethod.POST)
	public Tip getClassInfo(@RequestBody ClassinfoReq req) {

		req.checkOrder(ClassInfoVo.class);
		Page<ClassInfoVo> page = classInfoService.pageList(new Page<ClassInfoVo>(req.getPageNo(), req.getPageSize()), req);
		return SuccessTip.buildSuccess(page);
	}

	/**
	 * @api {GET} /restApi/scan/ueditor 百度编辑器
	 * @apiGroup scan
	 * @apiName ueditor
	 * @apiVersion 1.5.0
	 */
	@RequestMapping(value = "ueditor", method = RequestMethod.GET)
	public Object exe(HttpServletRequest request) {

		return JSON.parse(actionEnter.exec(request));
	}

	/**
	 * @api {GET} /restApi/scan/applyCooperate 申请合作
	 * @apiGroup scan
	 * @apiName applyCooperate
	 * @apiParam {String} applyName 联系人姓名
	 * @apiParam {String}contactTel 联系电话
	 * @apiParam {String} provinceCode 省
	 * @apiParam {String} cityCode 市
	 * @apiSuccessExample {json} Success-Response:
	 *                    {
	 *                    "applyName": "周",
	 *                    "cityCode": "110000",
	 *                    "contactTel": "17625320526",
	 *                    "provinceCode": "110101",
	 *                    "type": 0
	 *                    }
	 * @apiSuccess code 返回编码（200成功）
	 * @apiSuccess message 返回说明
	 * @apiVersion 1.5.0
	 */
	@RequestMapping(value = "applyCooperate", method = RequestMethod.POST)
	public Tip applyCooperate(@RequestBody @Valid ApplyCooperateReq applyCooperateReq) {

		applyCooperateService.addApplyCooperate(applyCooperateReq);
		return SuccessTip.buildSuccess();
	}

}
